package com.strive.common.utils;

import ma.glasnost.orika.MapperFacade;
import ma.glasnost.orika.MapperFactory;
import ma.glasnost.orika.impl.DefaultMapperFactory;
import org.apache.commons.compress.utils.Lists;
import org.springframework.util.CollectionUtils;

import java.util.ArrayList;
import java.util.Collection;
import java.util.List;

/**
 *
 */
public class CommonConverterUtil {

    private static MapperFactory mapperFactory = new DefaultMapperFactory.Builder().build();
    private static MapperFacade mapperFacade = null;

    static {
        CommonConverterUtil.mapperFacade = CommonConverterUtil.mapperFactory.getMapperFacade();
    }

    private CommonConverterUtil() {
    }

    public static MapperFacade getMapperFacade() {
        return CommonConverterUtil.mapperFacade;
    }

    public static <T> T map(Object sourceObject, Class<T> targetClass) {
        return CommonConverterUtil.mapperFacade.map(sourceObject, targetClass);
    }

    public static <T> List<T> mapList(Collection<?> sourceObjects, Class<T> targetClass) {
        List<T> result = Lists.newArrayList();
        if (sourceObjects != null && !sourceObjects.isEmpty()) {
            for (Object sourceObject : sourceObjects) {
                result.add(CommonConverterUtil.map(sourceObject, targetClass));
            }
        }
        return result;
    }

    public static <T> PagedListUtil<T> mapPagedList(PagedListUtil<?> sourcePagedList, Class<T> targetDataItemClass) {
        if (sourcePagedList == null) {
            return PagedListUtil.newMe();
        } else if (CollectionUtils.isEmpty(sourcePagedList.getData())) {
            return PagedListUtil.newMe(sourcePagedList.getPageNum(), sourcePagedList.getPageSize(),
                    sourcePagedList.getTotalCount(), new ArrayList<>());
        }

        List<T> mappedData = CommonConverterUtil.mapList(sourcePagedList.getData(), targetDataItemClass);
        return PagedListUtil.newMe(sourcePagedList.getPageNum(), sourcePagedList.getPageSize(),
                sourcePagedList.getTotalCount(), mappedData);
    }

    public static <T> PagedListUtil<T> mapPagedList(PagedListUtil<?> sourcePagedList, List<T> mappedData) {
        if (sourcePagedList == null) {
            return PagedListUtil.newMe();
        } else if (CollectionUtils.isEmpty(sourcePagedList.getData())) {
            return PagedListUtil.newMe(sourcePagedList.getPageNum(), sourcePagedList.getPageSize(),
                    sourcePagedList.getTotalCount(), new ArrayList<>());
        }

        return PagedListUtil.newMe(sourcePagedList.getPageNum(), sourcePagedList.getPageSize(),
                sourcePagedList.getTotalCount(), mappedData);
    }
}
